/*
 *    Copyright © OpenAtom Foundation.
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */

package com.inspur.edp.cef.repository.adaptoritem;

import com.inspur.edp.bef.api.lcp.LcpFactoryManagerUtils;
import com.inspur.edp.cef.api.RefObject;
import com.inspur.edp.cef.api.repository.GspDbType;
import com.inspur.edp.cef.api.repository.INestedRepository;
import com.inspur.edp.cef.api.repository.IRootRepository;
import com.inspur.edp.cef.api.repository.readerWriter.ICefReader;
import com.inspur.edp.cef.entity.condition.EntityFilter;
import com.inspur.edp.cef.entity.entity.IEntityData;
import com.inspur.edp.cef.repository.adaptor.EntityRelationalAdaptor;
import com.inspur.edp.cef.repository.adaptoritem.dbprocessor.DbProcessor;
import com.inspur.edp.cef.repository.dbcolumninfo.ColumnInfoUtils;
import com.inspur.edp.cef.repository.dbcolumninfo.DbColumnInfo;
import com.inspur.edp.cef.repository.dbcolumninfo.DbColumnInfoCollection;
import com.inspur.edp.cef.repository.dbcolumninfo.repoproccessor.AssociationRepoProcessor;
import com.inspur.edp.cef.repository.dbcolumninfo.repoproccessor.SimpleAssoUdtRepoProcessor;
import com.inspur.edp.cef.repository.exception.CefRepositoryException;
import com.inspur.edp.cef.repository.extend.RepoExtendManager;
import com.inspur.edp.cef.repository.readerwriter.CefMappingReader;
import com.inspur.edp.cef.repository.repo.BaseRootRepository;
import com.inspur.edp.cef.repository.utils.RepositoryUtil;
import com.inspur.edp.cef.spi.entity.AssociationInfo;
import com.inspur.edp.cef.spi.entity.info.propertyinfo.*;
import com.inspur.edp.cef.spi.entity.resourceInfo.builinImpls.CefEntityResInfoImpl;
import io.iec.edp.caf.i18n.framework.api.language.EcpLanguage;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class BaseAdaptorItem extends AdaptorItem{
    private final EntityRelationalReposAdaptor adaptor;
    private final int version;

    private HashMap<String, Integer> baseMapping = new HashMap<>();
    protected static Logger logger = LoggerFactory.getLogger(EntityRelationalAdaptor.class);

    public BaseAdaptorItem(EntityRelationalReposAdaptor adaptor)
    {
        this(adaptor,0);
    }

    public BaseAdaptorItem(EntityRelationalReposAdaptor adaptor,int version)
    {
        this.adaptor = adaptor;
        this.version = version;
        initAssociations();
        initColumnCache();
    }

    protected GspDbType getGspDbType(){
        return adaptor.getGspDbType();
    }

    protected DbProcessor getDbProcessor(){
        return adaptor.getDbProcessor();
    }

    public  final CefEntityResInfoImpl getEntityResInfo()
    {return adaptor.getEntityResInfo();}

    public HashMap<java.lang.String,java.lang.String> getAssosPropDBMapping(String propName){
        if(version==0)
            return new HashMap<>();
        DbColumnInfo dbColumnInfo=this.getContainColumns().getItem(propName);
        DataTypePropertyInfo dataTypePropertyInfo=null;
        if(dbColumnInfo==null||dbColumnInfo.getDataTypePropertyInfo()==null)
        {
            dataTypePropertyInfo  =this.getEntityResInfo().getEntityTypeInfo().getPropertyInfo(propName);
        }
        else
            dataTypePropertyInfo=dbColumnInfo.getDataTypePropertyInfo();
        if(dataTypePropertyInfo.getObjectInfo() instanceof  ComplexUdtPropertyInfo)
        {
            return ((ComplexUdtPropertyInfo)dataTypePropertyInfo.getObjectInfo()).getPropAndRefMapping();
        }
        if(dataTypePropertyInfo.getObjectInfo() instanceof  AssocationPropertyInfo)
        {
            return ((AssocationPropertyInfo)dataTypePropertyInfo.getObjectInfo()).getAssDbMapping();
        }
        if(dataTypePropertyInfo.getObjectInfo() instanceof SimpleAssoUdtPropertyInfo)
            return ((SimpleAssoUdtPropertyInfo)dataTypePropertyInfo.getObjectInfo()).getAssoInfo().getAssDbMapping();
        return new HashMap<>();
    }

    @Override
    public String getTableAlias() {
        return this.adaptor.getTableAlias();
    }

    @Override
    public void setTableAlias(String value) {
        this.adaptor.setTableAlias(value);
    }

    private void initColumnCache(){
        if(!getSqlCache().isColumnInit()){
            synchronized (getSqlCache().getContainColumns()){
                if(!getSqlCache().isColumnInit()){
                    initColumns();
                    if(version>0)
                        initAssociationDbMappings(getEntityResInfo());
                    getSqlCache().setColumnInit(true);
                }
            }
        }
    }

    @Override
    protected void initColumns() {
        initColumns(getEntityResInfo());
    }

    private void initColumns(CefEntityResInfoImpl entityResInfo) {
        if(entityResInfo==null)
            throw new CefRepositoryException("ResourceInfo为空。");
        for (Map.Entry<String, DataTypePropertyInfo> propertyInfoEntry : entityResInfo
                .getEntityTypeInfo().getPropertyInfos().entrySet()) {
            ColumnInfoUtils.convertPropertyInfoToColumnInfo(propertyInfoEntry.getValue(),entityResInfo,this);

        }
    }

    private void initAssociationDbMappings(
            CefEntityResInfoImpl entityResInfo) {
        if(entityResInfo.isInitingAssMapping())
            return;
        try {
            entityResInfo.setInitingAssMapping(true);
            for (Map.Entry<String, DataTypePropertyInfo> dataTypePropertyInfo : entityResInfo
                    .getEntityTypeInfo().getPropertyInfos().entrySet()) {
                if (dataTypePropertyInfo.getValue().getObjectInfo() instanceof AssocationPropertyInfo) {
                    AssocationPropertyInfo associationInfo = (AssocationPropertyInfo) dataTypePropertyInfo
                            .getValue().getObjectInfo();

                    HashMap<String, String> map = new HashMap<>();
                    EntityRelationalAdaptor adapter = ((BaseRootRepository) this
                            .getAssociation(dataTypePropertyInfo.getValue().getPropertyName())
                            .getRefRepository())
                            .getEntityDac(associationInfo.getAssociationInfo().getNodeCode())
                            .getEntityAdaptor();
                    for (Map.Entry<String, DataTypePropertyInfo> refProperty : associationInfo
                            .getAssociationInfo()
                            .getRefPropInfos().entrySet()) {
                        RefDataTypePropertyInfo refDataTypePropertyInfo = (RefDataTypePropertyInfo) refProperty
                                .getValue();
                        map.put(refDataTypePropertyInfo.getRefPropertyName(),
                                refDataTypePropertyInfo.getPropertyName());
                        //多值udt 是否判断单列和多列？
                        if(refDataTypePropertyInfo.getObjectInfo() instanceof ComplexUdtPropertyInfo){
                            for(Map.Entry<String, String> mappingEntry: ((ComplexUdtPropertyInfo)refDataTypePropertyInfo.getObjectInfo()).getPropAndRefMapping().entrySet()){
                                map.put(mappingEntry.getValue(), dataTypePropertyInfo.getKey() + "_" + mappingEntry.getValue());
                            }
                        }
                    }
                    map.put(associationInfo.getAssociationInfo().getPrivateSourceColumn(),
                            associationInfo.getAssociationInfo().getPrivateTargetColumn());
                    for (Map.Entry<String, DataTypePropertyInfo> refProperty : associationInfo
                            .getAssociationInfo()
                            .getRefPropInfos().entrySet()) {
                        RefDataTypePropertyInfo refDataTypePropertyInfo = (RefDataTypePropertyInfo) refProperty
                                .getValue();
//                        if (refDataTypePropertyInfo.getObjectType() != ObjectType.Association)
//                            continue;
                        if(refDataTypePropertyInfo.getObjectInfo()==null)
                            continue;
                        if(refDataTypePropertyInfo.getObjectInfo() instanceof SimpleAssoUdtPropertyInfo) {
                            HashMap<String, String> refPropMap = adapter
                                    .getAssosPropDBMapping(refDataTypePropertyInfo.getRefPropertyName());
                            if (refPropMap != null) {
                                for (Map.Entry<String, String> item : refPropMap.entrySet()) {
                                    if (map.containsKey(item.getValue()) == false) {
                                        map.put(item.getValue(),
                                                dataTypePropertyInfo.getValue().getPropertyName() + "_" + item
                                                        .getValue());
                                    }
                                }
                            }
                        }
                        else if(refDataTypePropertyInfo.getObjectInfo() instanceof  AssocationPropertyInfo)
                        {
                            HashMap<String, String> refPropMap = adapter
                                    .getAssosPropDBMapping(refDataTypePropertyInfo.getRefPropertyName());
                            if (refPropMap != null) {
                                for (Map.Entry<String, String> item : refPropMap.entrySet()) {
                                    if (map.containsKey(item.getValue()) == false) {
                                        map.put(item.getValue(),
                                                dataTypePropertyInfo.getValue().getPropertyName() + "_" + item
                                                        .getValue());
                                    }
                                }
                            }
                        }
                    }
                    associationInfo.setAssDbMapping(map);
                } else if (dataTypePropertyInfo.getValue().getObjectInfo() instanceof SimpleAssoUdtPropertyInfo) {
                    SimpleAssoUdtPropertyInfo simpleAssoUdtPropertyInfo = (SimpleAssoUdtPropertyInfo) dataTypePropertyInfo.getValue().getObjectInfo();
                    AssocationPropertyInfo associationInfo = simpleAssoUdtPropertyInfo.getAssoInfo();

                    HashMap<String, String> map = new HashMap<>();

                    for (Map.Entry<String, DataTypePropertyInfo> refProperty : associationInfo
                            .getAssociationInfo()
                            .getRefPropInfos().entrySet())
                    {
                        RefDataTypePropertyInfo refDataTypePropertyInfo = (RefDataTypePropertyInfo) refProperty
                                .getValue();
                        if(refDataTypePropertyInfo.getObjectInfo() instanceof ComplexUdtPropertyInfo){
                            for(Map.Entry<String, String> mappingEntry: ((ComplexUdtPropertyInfo)refDataTypePropertyInfo.getObjectInfo()).getPropAndRefMapping().entrySet()){
                                map.put(simpleAssoUdtPropertyInfo.getUdtConfigId().substring(simpleAssoUdtPropertyInfo.getUdtConfigId().lastIndexOf(".")+1)+"_"+ mappingEntry.getValue(), dataTypePropertyInfo.getKey() + "_" + mappingEntry.getValue());
                            }
                        }
                    }
//                EntityRelationalAdaptor adapter = ((BaseRootRepository) this
//                    .getAssociation(dataTypePropertyInfo.getValue().getPropertyName())
//                    .getRefRepository())
//                    .getEntityDac(associationInfo.getAssociationInfo().getNodeCode())
//                    .getEntityAdaptor();
//                BaseNestedRepository baseNestedRepository=((BaseNestedRepository)this.getNestedRepo(simpleAssoUdtPropertyInfo.getUdtConfigId()));
//                for (Map.Entry<String, DataTypePropertyInfo> refProperty : associationInfo
//                    .getAssociationInfo()
//                    .getRefPropInfos().entrySet()) {
//                    RefDataTypePropertyInfo refDataTypePropertyInfo = (RefDataTypePropertyInfo) refProperty
//                        .getValue();
//                    map.put(refDataTypePropertyInfo.getRefPropertyName(),
//                        refDataTypePropertyInfo.getPropertyName());
//                }
//
//                for (Map.Entry<String, DataTypePropertyInfo> refProperty : associationInfo
//                    .getAssociationInfo()
//                    .getEnrichedRefPropInfos().entrySet()) {
//                    RefDataTypePropertyInfo refDataTypePropertyInfo = (RefDataTypePropertyInfo) refProperty
//                        .getValue();
//                    map.put(refDataTypePropertyInfo.getRefPropertyName(),
//                        refDataTypePropertyInfo.getPropertyName());
//                }
//
//                map.put(associationInfo.getAssociationInfo().getPrivateSourceColumn(),
//                    associationInfo.getAssociationInfo().getPrivateTargetColumn());
//                for (Map.Entry<String, DataTypePropertyInfo> refProperty : associationInfo
//                    .getAssociationInfo()
//                    .getRefPropInfos().entrySet()) {
//                    RefDataTypePropertyInfo refDataTypePropertyInfo = (RefDataTypePropertyInfo) refProperty
//                        .getValue();
//                    HashMap<String, String> refPropMap = baseNestedRepository
//                        .getAssosPropDBMapping(refDataTypePropertyInfo.getRefPropertyName());
//                    if (refPropMap != null) {
//                        for (Map.Entry<String, String> item : refPropMap.entrySet()) {
//                            if (map.containsKey(item.getKey()) == false) {
//                                map.put(item.getValue(),
//                                    dataTypePropertyInfo.getValue().getPropertyName() + "_" + item
//                                        .getValue());
//                            }
//                        }
//                    }
//                }
                    map.putAll(simpleAssoUdtPropertyInfo.getMapping());
                    associationInfo.setAssDbMapping(map);
                }
            }
        }
        finally {
            entityResInfo.setInitingAssMapping(false);
        }

    }

    @Override
    protected void initAssociations() {
        initAssociations(getEntityResInfo());
    }

    private void initAssociations(CefEntityResInfoImpl entityResInfo) {
        for (Map.Entry<String,DataTypePropertyInfo> dataTypePropertyInfoEntry:entityResInfo.getEntityTypeInfo().getPropertyInfos().entrySet())
        {
            DataTypePropertyInfo dataTypePropertyInfo=dataTypePropertyInfoEntry.getValue();
//            if(dataTypePropertyInfo.getObjectType()!= ObjectType.Association)
//                continue;
            if(dataTypePropertyInfo.getObjectInfo() instanceof SimpleAssoUdtPropertyInfo)
                initAssUdtAssociations(dataTypePropertyInfo);
            else if(dataTypePropertyInfo.getObjectInfo() instanceof  AssocationPropertyInfo)
                initAssociations(dataTypePropertyInfo);
        }
    }

    private void initAssociations(DataTypePropertyInfo dataTypePropertyInfo) {
        com.inspur.edp.cef.spi.entity.AssociationInfo associationInfo = ((AssocationPropertyInfo) dataTypePropertyInfo
                .getObjectInfo()).getAssociationInfo();
        initAssociationByAssociationInfo(associationInfo,dataTypePropertyInfo);
    }

    private void initAssociationByAssociationInfo(
            AssociationInfo associationInfo, DataTypePropertyInfo dataTypePropertyInfo) {
        IRootRepository repository = LcpFactoryManagerUtils.getBefRepositoryFactory()
                .createRepository(associationInfo.getConfig());
        HashMap<String, String> map = new HashMap<>();
        addRefPropertyMap(associationInfo, map,dataTypePropertyInfo);
        //这个里面的source和target跟resourceinfo里面的source和target正好相反
//        addAssociationInfo(associationInfo.getNodeCode(),associationInfo.getPrivateTargetColumn(),associationInfo.getPrivateSourceColumn(),repository,map,associationInfo.getConfig());
        addAssociationInfo(associationInfo, repository,map);
    }

    private void addRefPropertyMap(AssociationInfo associationInfo,
                                   HashMap<String, String> map, DataTypePropertyInfo dataTypePropertyInfo) {
        if (associationInfo.getRefPropInfos() != null)
            for (Map.Entry<String, DataTypePropertyInfo> refDataTypePropertyInfoEntry : associationInfo
                    .getRefPropInfos().entrySet()) {
                if(refDataTypePropertyInfoEntry.getValue() instanceof  RefDataTypePropertyInfo)
                    addRefColumnToMap((RefDataTypePropertyInfo) refDataTypePropertyInfoEntry.getValue(),
                            map);
                else
                {
                    map.put(refDataTypePropertyInfoEntry.getValue().getPropertyName(), refDataTypePropertyInfoEntry.getValue().getPropertyName().replaceFirst(dataTypePropertyInfo.getPropertyName()+"_",""));
                }
            }
        if (associationInfo.getEnrichedRefPropInfos() != null)
            for (Map.Entry<String, DataTypePropertyInfo> refDataTypePropertyInfoEntry : associationInfo
                    .getEnrichedRefPropInfos().entrySet()) {
                if(refDataTypePropertyInfoEntry.getValue() instanceof  RefDataTypePropertyInfo)
                    addRefColumnToMap((RefDataTypePropertyInfo) refDataTypePropertyInfoEntry.getValue(),
                            map);
                else
                {
                    map.put(refDataTypePropertyInfoEntry.getValue().getPropertyName(), refDataTypePropertyInfoEntry.getValue().getPropertyName().replaceFirst(dataTypePropertyInfo.getPropertyName()+"_",""));
                }
            }
    }

    private void addRefColumnToMap(RefDataTypePropertyInfo value, HashMap<String, String> map) {
        map.put(value.getPropertyName(), value.getRefPropertyName());
    }

    private void initAssUdtAssociations(DataTypePropertyInfo dataTypePropertyInfo) {
        com.inspur.edp.cef.spi.entity.AssociationInfo associationInfo=((SimpleAssoUdtPropertyInfo)dataTypePropertyInfo.getObjectInfo()).getAssoInfo().getAssociationInfo();
        initAssociationByAssociationInfo(associationInfo, dataTypePropertyInfo);
    }

    @Override
    public DbColumnInfoCollection getContainColumns() {
        return getSqlCache().getContainColumns();
    }

    @Override
    public String getQueryFields(EntityFilter entityFilter, HashMap<String, Integer> mapping){
        if (entityFilter != null && entityFilter.getFieldsFilter() != null && entityFilter.getFieldsFilter().isUseFieldsCondition()){
            return RepoExtendManager.buildQueryFields(getTableAlias(), this.getContainColumns(), entityFilter, mapping);
        }
        else{
            if(!getSqlCache().getQueryFieldsMap().containsKey(getGspDbType().toString())){
                synchronized (getSqlCache().getQueryFieldsMap()){
                    if(!getSqlCache().getQueryFieldsMap().containsKey(getGspDbType().toString())){

                        String queryFields = RepoExtendManager.buildQueryFields(getTableAlias(), this.getContainColumns(), entityFilter, mapping);
                        if(!getSqlCache().getQueryMappingMap().containsKey(getGspDbType().toString())){
                            getSqlCache().getQueryMappingMap().put(getGspDbType().toString(), mapping);
                        }
                        getSqlCache().getQueryFieldsMap().put(getGspDbType().toString(), queryFields);
                    }
                    else{
                        if(getSqlCache().getQueryMappingMap().containsKey(getGspDbType().toString())){
                            for(Map.Entry<String, Integer>  item: getSqlCache().getQueryMappingMap().get(getGspDbType().toString()).entrySet()){
                                mapping.put(item.getKey(), item.getValue());
                            }
                        }
                    }
                }
            }else {
                if(mapping == null)
                    mapping = new HashMap<>();
                //todo 这个地方直接赋值 返回到调用处不好使。。后续研究原因
                for(Map.Entry<String, Integer>  item: getSqlCache ().getQueryMappingMap().get(getGspDbType().toString()).entrySet()){
                    mapping.put(item.getKey(), item.getValue());
                }
            }
        }
        return getSqlCache().getQueryFieldsMap().get(getGspDbType().toString());
    }

    @Override
    public String getQueryFieldsWithOutCache(EntityFilter entityFilter, HashMap<String, Integer> mapping){
        return RepoExtendManager.buildQueryFields(getTableAlias(), this.getContainColumns(), entityFilter, mapping);
    }
    public   AdaptorItemSqlCache getSqlCache()
    {
        return adaptor.getSqlSnippetCache().getAdaptorItemSqlCache();
    }

    @Override
    public Map<Integer, String> getInsertMultiIndexMap(){
        return getSqlCache().getInsertMultiIndexMap().get(getGspDbType().toString());
    }
    @Override
    public String getInsertFields(boolean isMultiData){
        if(isMultiData){
            String insertFields = "";
            if(!getSqlCache().getInsertFieldsWithMultiMap().containsKey(getGspDbType().toString())){
                synchronized (getSqlCache().getInsertFieldsWithMultiMap()){
                    if(!getSqlCache().getInsertFieldsWithMultiMap().containsKey(getGspDbType().toString())){
                        insertFields = getInsertFields_MultiLanguage();
                        getSqlCache().getInsertFieldsWithMultiMap().put(getGspDbType().toString(), insertFields);
                    }
                }
            }
            return getSqlCache().getInsertFieldsWithMultiMap().get(getGspDbType().toString());
        }
        else {
            String insertFields = "";
            if(!getSqlCache().getInsertFieldsMap().containsKey(getGspDbType().toString())){
                synchronized (getSqlCache().getInsertFieldsMap()){
                    if(!getSqlCache().getInsertFieldsMap().containsKey(getGspDbType().toString())){
                        insertFields = getInsertFields();
                        getSqlCache().getInsertFieldsMap().put(getGspDbType().toString(), insertFields);
                    }
                }
            }
            return getSqlCache().getInsertFieldsMap().get(getGspDbType().toString());
        }
    }

    private String getInsertFields_MultiLanguage() {
        StringBuilder fields = new StringBuilder();
        // 初始化
        insertMultiIndexMap = new HashMap<>();
        List<EcpLanguage> currentEnableLanguages = RepositoryUtil.getCurrentEnabledLanguages();
        for (DbColumnInfo containColumn : getContainColumns()) {
            if (containColumn.getIsAssociateRefElement()) {
                continue;
            }
            if(containColumn.isVirtual()){
                continue;
            }
            // 多语单独处理
            if (containColumn.getIsMultiLang()) {
                for (EcpLanguage language : currentEnableLanguages) {
                    String dboalias = RepositoryUtil
                            .FormatMuliLangColumnName(containColumn.getDbColumnName(), language);
                    String alias = RepositoryUtil
                            .FormatMuliLangColumnName(containColumn.getColumnName(), language);
                    // 不使用过滤，则全部添加
                    if (fields.length() > 0) {
                        fields.append(",");
                    }
                    fields.append(dboalias);
                    if (insertMultiIndexMap.containsValue(alias)) {
                        throw new CefRepositoryException("列名重复");
                    }
                    insertMultiIndexMap.put(insertMultiIndexMap.size(), alias);
                }
                continue;
            }
            if (fields.length() > 0) {
                fields.append(",");
            }
            fields.append(containColumn.getDbColumnName());
            if (!insertMultiIndexMap.containsKey(containColumn.getColumnName())) {
                insertMultiIndexMap
                        .put(insertMultiIndexMap.size(), containColumn.getColumnName());
            }
        }
        getSqlCache().getInsertMultiIndexMap().put(getGspDbType().toString(), insertMultiIndexMap);
        return fields.toString();
    }

    @Override
    protected String getInsertValues(boolean isMultiData, RefObject<Integer> valuesCount) {
        if(isMultiData){
            if(!getSqlCache().getInsertFieldValueWithMultiMap().containsKey(getGspDbType().toString())){
                synchronized (getSqlCache().getInsertFieldValueWithMultiMap()){
                    if(!getSqlCache().getInsertFieldValueWithMultiMap().containsKey(getGspDbType().toString())){
                        RefObject<Integer> tempValuesCount = new RefObject<Integer>(valuesCount.argvalue);
                        String insertValues = "";
                        insertValues = getInsertValues_MultiLanguage(tempValuesCount);
                        getSqlCache().getMultiValusCount().put(getGspDbType().toString(), tempValuesCount);
                        getSqlCache().getInsertFieldValueWithMultiMap().put(getGspDbType().toString(), insertValues);
                    }
                }
            }
            valuesCount.argvalue = getSqlCache().getMultiValusCount().get(getGspDbType().toString()).argvalue;
            return getSqlCache().getInsertFieldValueWithMultiMap().get(getGspDbType().toString());
        }
        else {
            if(!getSqlCache().getInsertFieldValueMap().containsKey(getGspDbType().toString())){
                synchronized (getSqlCache().getInsertFieldValueMap()){
                    if(!getSqlCache().getInsertFieldValueMap().containsKey(getGspDbType().toString())){
                        RefObject<Integer> tempValuesCount = new RefObject<Integer>(valuesCount.argvalue);
                        String insertValues = "";
                        insertValues = getInsertValues(tempValuesCount);
                        getSqlCache().getValusCount().put(getGspDbType().toString(), tempValuesCount);
                        getSqlCache().getInsertFieldValueMap().put(getGspDbType().toString(), insertValues);
                    }
                }
            }
            valuesCount.argvalue = getSqlCache().getValusCount().get(getGspDbType().toString()).argvalue;
            return getSqlCache().getInsertFieldValueMap().get(getGspDbType().toString());
        }
    }

    private String getInsertValues_MultiLanguage(RefObject<Integer> valuesCount) {
        if (insertMultiIndexMap.isEmpty()) {
            throw new CefRepositoryException("包含多语信息的insertSql的列信息未组织");
        }
        StringBuilder values = new StringBuilder();
        for (Map.Entry<Integer, String> entrySet : insertMultiIndexMap.entrySet()) {
            if (valuesCount.argvalue > 0) {
                values.append(",");
            }
            values.append("?");
            valuesCount.argvalue = valuesCount.argvalue + 1;
        }
        return values.toString();
    }

    @Override
    public Object readProperty(String propertyName, ICefReader reader) {
        DataTypePropertyInfo dataTypePropertyInfo=getEntityResInfo().getEntityTypeInfo().getPropertyInfo(propertyName,true);
        if(dataTypePropertyInfo!=null&&dataTypePropertyInfo instanceof RefDataTypePropertyInfo)
        {
            RefDataTypePropertyInfo refDataTypePropertyInfo= (RefDataTypePropertyInfo) dataTypePropertyInfo;
            DataTypePropertyInfo dataTypePropertyInfo1=refDataTypePropertyInfo.getBelongPropertyInfo();
            if(dataTypePropertyInfo1==null)
                throw new CefRepositoryException("找不到带出属性"+refDataTypePropertyInfo.getPropertyName()+"所属的属性。");
            if(dataTypePropertyInfo1.getObjectType() == ObjectType.Association)
            {
                return new AssociationRepoProcessor().readRefProperty(getContainColumns().getItem(dataTypePropertyInfo1.getPropertyName()),this,reader,refDataTypePropertyInfo.getRefPropertyName());
            }
            if(dataTypePropertyInfo1.getObjectInfo() instanceof  SimpleAssoUdtPropertyInfo)
            {
                return new SimpleAssoUdtRepoProcessor().readProperty(getContainColumns().getItem(dataTypePropertyInfo1.getPropertyName()),getDbProcessor(),this,reader,refDataTypePropertyInfo.getRefPropertyName());
            }
        }
        if(getContainColumns().contains(propertyName))
        {
            return getContainColumns().getItem(propertyName).readProperty(reader,this,getDbProcessor());
        }
        if(dataTypePropertyInfo==null){
            throw new CefRepositoryException("找不到对应的列信息，当前实体："+getEntityResInfo().getEntityCode()+",要查找的列："+propertyName);
        }
        if(dataTypePropertyInfo.getObjectInfo() instanceof ComplexUdtPropertyInfo)
        {
            ComplexUdtPropertyInfo complexUdtPropertyInfo= (ComplexUdtPropertyInfo) dataTypePropertyInfo.getObjectInfo();
            CefMappingReader mappingReader=new CefMappingReader(complexUdtPropertyInfo.getPropAndRefMapping(),reader);
            INestedRepository u1Repos=getNestedRepository(complexUdtPropertyInfo.getUdtConfigId());
            return u1Repos.readData(mappingReader);
        }
        else
        {throw new CefRepositoryException("");}
    }

    @Override
    protected void setEntityValue(ICefReader reader, IEntityData entityData) {
        for(DbColumnInfo dbColumnInfo:getContainColumns())
        {
            if(dbColumnInfo.getDataTypePropertyInfo()==null)
                continue;
            if(dbColumnInfo.getDataTypePropertyInfo() instanceof RefDataTypePropertyInfo)
                continue;
            //TODO: udt字段reader里没有也要执行赋值, 否则acc不支持.
            if(reader.hasProperty(dbColumnInfo.getDataTypePropertyInfo().getPropertyName())
                    ||dbColumnInfo.getDataTypePropertyInfo().getObjectType() == ObjectType.UDT)
                entityData.setValue(dbColumnInfo.getDataTypePropertyInfo().getPropertyName(),dbColumnInfo.readProperty(reader,this,getDbProcessor()));
        }
        for (Map.Entry<String, DataTypePropertyInfo> propertyInfo:getEntityResInfo().getEntityTypeInfo().getPropertyInfos().entrySet())
        {
            if(propertyInfo.getValue().getObjectInfo() instanceof  ComplexUdtPropertyInfo)
            {
                ComplexUdtPropertyInfo complexUdtPropertyInfo= (ComplexUdtPropertyInfo) propertyInfo.getValue().getObjectInfo();
                CefMappingReader mappingReader=new CefMappingReader(complexUdtPropertyInfo.getPropAndRefMapping(),reader);
                INestedRepository u1Repos=getNestedRepository(complexUdtPropertyInfo.getUdtConfigId());
                entityData.setValue(propertyInfo.getValue().getPropertyName(),u1Repos.readData(mappingReader));
            }
        }
    }
}
